﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using PServiceBus.Core.Interface;
using PServiceBus.Core.Runtime.Transports;
using PServiceBus.Core.Runtime.Extensions;
using System.Net;
using System.Runtime.Serialization;
using System.ComponentModel.Composition;

namespace PServiceBus.Transports {
    [Serializable]
    [DataContract]
    [Export(typeof(ITransport))]
    public class BasicHttpTransport : ITransport {
        [DataMember]
        public string Url { get; set; }
        [DataMember]
        public Dictionary<string, string> Headers { get; set; }
        [DataMember]
        public string ContentType { get; set; }
        [DataMember]
        public int? ContentLength { get; set; }
        [DataMember]
        public string Method { get; set; }

        #region ITransport Members
        [DataMember]
        public TransportFormat Format { get; set; }

        public TransportResponse Send(string message, Dictionary<string, object> messageStructure) {
            var tranResponse = TransportResponse.New<BasicHttpTransport>();
            try {
                if (!Url.Exists()) throw new Exception("Web url does not exist!");
                Headers = Headers ?? new Dictionary<string, string>();
                var buffer = Encoding.UTF8.GetBytes(message);
                var request = WebRequest.Create(Url);
                request.Method = Method ?? "POST";
                request.ContentType = ContentType ?? 
                    (Format == TransportFormat.Xml ? "text/xml" :
                    Format == TransportFormat.Json ? "application/json" : "text/plain");
                request.ContentLength = Math.Max((ContentLength ?? 0), buffer.Length);
                if (Headers.Count > 0) {
                    request.Headers = new WebHeaderCollection();
                    foreach (var header in Headers) request.Headers[header.Key] = header.Value;
                }
                using (var requestStream = request.GetRequestStream()) {
                    requestStream.Write(buffer, 0, buffer.Length);
                    requestStream.Flush();
                }

                var response = request.GetResponse();
                response.Close();

                tranResponse.Success = true;
            } catch (Exception ex) {
                tranResponse.Message = ex.ToString();
            }
            return tranResponse;
        }

        #endregion
    }
}
